<?php
/**
 * PddPresetField.php class file.
 * @author wudg <544038230@qq.com>
 * @date 2021/1/6- 上午10:40
 */

namespace common\jobs\copy\tools;


use common\constants\FilterConst;
use common\exception\CopyException;
use common\helpers\CopyHelper;
use common\jobs\models\PddFilterTpl;
use common\jobs\models\PddGoodsCats;
use common\jobs\services\CopyService;
use common\components\api\isv\Goods;
use common\helpers\ImagesHelper;
use common\helpers\StringHelper;
use common\models\com\ComSpider;
use console\components\helpers\ConsoleHelper;
use common\components\misc\ImportLogger;
use Swoole\Coroutine\WaitGroup;
use Yii;
class PddFilterBasic
{

    /**
     * 详情图图片数量最大值
     * @var int
     */
    public $detailImgMaxNum = 20;


    /**
     * 轮播图图片最大张数
     * @var int
     */
    public $carouselImgMaxNum = 10;

    /**
     * 导入日志
     * @var ImportLogger
     */
    public $logger;


    public $spiderId;


    /**
     * 允许的附件类型
     * @var array
     */
    public $allowImgExt = ['jpg','png','JPG','PNG','JPEG','jpeg'];


    public function __construct(ImportLogger $logger,$spiderId)
    {
        $this->logger = $logger;

        $this->allowImgExt = Yii::$app->params['pddImageExt'];

        $this->spiderId = $spiderId;
    }


    /**
     * 类目匹配
     * @param ComSpider $sourceData
     * @param PddFilterTpl $filter
     * @param Goods $goodsIsv
     * @param int $mall_id
     * @return int|null
     * @throws CopyException
     * @throws \common\exception\ServicesException
     */
    public function setCid(ComSpider $sourceData,PddFilterTpl $filter,Goods $goodsIsv,int $mall_id)
    {
        switch ($filter->settings['basic']['cid_check'])
        {
            //没找到类目信息，再 匹配一次
            case 1:
                $catInfo = PddGoodsCats::findOne(['cat_id'=>$sourceData->extend_data['cid']]);
                $cat_id = null;
                if(!$catInfo || $catInfo->is_parent == 1)
                {
                    $mappingCats = $goodsIsv->pddGoodsOuterCatMappingGet([
                        'outer_cat_id' => $sourceData->extend_data['cid'],
                        'outer_cat_name' => '',
                        'outer_goods_name' => $sourceData->extend_data['title'],
                    ],$mall_id);

                    if(isset($mappingCats['cat_id3']) && $mappingCats['cat_id3'] != 0)
                    {
                        $cat_id = $mappingCats['cat_id3'];
                    }
                    if(isset($mappingCats['cat_id4']) && $mappingCats['cat_id4'] != 0)
                    {
                        $cat_id = $mappingCats['cat_id4'];
                    }

                    if(!$cat_id && $filter->settings['basic']['not_cid_do'] == 1)
                    {
                        throw new CopyException('【规则过滤】未匹配到类目并设定了跳过');
                    }elseif(!$cat_id && $filter->settings['basic']['not_cid_do'] == 2)
                    {
                        if(!isset($filter->settings['basic']['not_cid_nodes']['cid']))
                        {
                            throw new CopyException('【规则过滤】未匹配到类目且自定义的类目未设置');
                        }
                        $cat_id = $filter->settings['basic']['not_cid_nodes']['cid'];
                    }
                    if(!$cat_id)
                    {
                        throw new CopyException('类目分析失败');
                    }
                }else{
                    $cat_id = $catInfo->cat_id;
                }
                break;
            //自定义类目
            case 2:
                if(!isset($filter->settings['basic']['cid_custom_nodes']['id']))
                {
                    throw new CopyException('【规则过滤】选定了自定义类目，但未设置类目信息');
                }
                $cat_id = $filter->settings['basic']['cid_custom_nodes']['id'];
                break;
            default:
                throw new CopyException('类目匹配失败,请确认配置信息是否正确');
        }
        return $cat_id;
    }


    /**
     * 预设字段
     * @param ComSpider $sourceData
     * @param PddFilterTpl $filter
     * @return array
     * @throws CopyException
     */
    public function presetField(ComSpider $sourceData,PddFilterTpl $filter)
    {

        $copyData = [];
        //商品类型
        $copyData['goods_type'] = $filter->settings['basic']['goods_type'];

        if(empty($filter->settings['basic']['cost_template_id']))
        {
            throw new CopyException('搬家配置未设置运费模板');
        }


        //国家ID
        $copyData['country_id'] = 0;

        //第三方商品来源
        $copyData['out_source_type'] = $sourceData->platform;

        //第三方商品Id
        $copyData['out_source_goods_id'] = $sourceData->plat_id;

        //运费模板
        $copyData['cost_template_id'] = $filter->settings['basic']['cost_template_id'];
        //是否预售
        $copyData['is_pre_sale'] = $filter->settings['basic']['copy_goods_status'] == 4 ? 'true' : 'false';
        //是否假一罚十
        $copyData['is_folt'] = $filter->settings['basic']['is_folt'] == 1 ? 'true' : 'false';

        //是否二手商品
        $copyData['second_hand'] = $filter->settings['basic']['second_hand'] == 1 ? 'false' : 'true';
        //发货方式。0：无物流发货；1：有物流发货。
//        $this->copyData['delivery_type'] = $this->filter->settings['basic']['delivery_type'];
        //团购人数
        $copyData['customer_num'] = $filter->settings['basic']['customer_num'];
        //限购次数
        $copyData['buy_limit'] = $filter->settings['basic']['buy_limit'];
        //单次限购
        $copyData['order_limit'] = $filter->settings['basic']['order_limit'];
        //坏果包赔
//        $this->copyData['bad_fruit_claim'] = $this->filter->settings['basic']['bad_fruit_claim'];
        //7天无理由包退换
        $copyData['is_refundable'] = $filter->settings['basic']['is_refundable'] == 1 ? 'true' : 'false';

        //预售商品才需要设置发货时间
        if($copyData['is_pre_sale'] == 'true')
        {
            //预售时间
            $copyData['pre_sale_time'] = strtotime($filter->settings['basic']['pre_sale_time']) + 86399;
        }
        //发货承诺时间
        $copyData['shipment_limit_second'] = FilterConst::transShipmentSecond($filter->settings['basic']['shipment_limit_second']);
        //市场价
        $copyData['market_price'] = PddSpec::marketPrice($sourceData->extend_data['prices']  ,$filter->settings['price']);


        return $copyData;
    }


    /**
     * 商品轮播图 和商品视频数据
     * @param ComSpider $sourceData
     * @param CopyService $copyServer
     * @param PddFilterTpl $filter
     * @param int $mall_id
     * @param string $mainWater
     * @return array
     * @throws CopyException
     * @since  商品轮播图下载改成协程模式，流程改成先全部下载到本地，再一个个上传到服务端
     * @throws \yii\base\Exception
     */
    public function carousel(ComSpider $sourceData,CopyService $copyServer,PddFilterTpl $filter,int $mall_id,$mainWater = null)
    {

        $copyData = [];
        $carouselGallery = @$sourceData->extend_data['pics'];

        $carouseNum = count($carouselGallery);
        if(!$carouseNum)
        {
            throw new CopyException('未检测到商品轮播图');
        }

        $copyData['carousel_gallery'] = [];


        $imagesSetting = @$filter->settings['images'];

        //头部删除
        if(isset($imagesSetting['del_pic_pre_num']) && $imagesSetting['del_pic_pre_num'] > 0)
        {
            $delPicPreNum = intval($imagesSetting['del_pic_pre_num']);
            if($carouseNum > $delPicPreNum && $delPicPreNum > 0)
            {
                array_splice($carouselGallery,0,$delPicPreNum);
            }
        }
        //尾部删除
        if(isset($imagesSetting['del_pic_after_num']) && $imagesSetting['del_pic_after_num'] > 0)
        {
            $carouseNum = count($carouselGallery);
            $delPicAfterNum = intval($imagesSetting['del_pic_after_num']);
            if($carouseNum > $delPicAfterNum && $delPicAfterNum > 0)
            {
                array_splice($carouselGallery,-intval($delPicAfterNum));
            }
        }
        //自定义删除
        if(isset($imagesSetting['del_pic_custom_num']) && !empty($imagesSetting['del_pic_custom_num']))
        {
            $delPicCustomNum = explode(',',$imagesSetting['del_pic_custom_num']);
            if(count($delPicCustomNum))
            {
                foreach($delPicCustomNum as $num)
                {
                    if(isset($carouselGallery[$num]))
                    {
                        unset($carouselGallery[$num]);
                    }
                }
            }
        }
        if(isset($imagesSetting['custom_main_area']) && !empty($imagesSetting['custom_main_area']))
        {
            switch ($imagesSetting['custom_main_area'])
            {
                case 1: //将第N张和第一张调换
                    if(isset($imagesSetting['move_main_pic']) && !empty($imagesSetting['move_main_pic']))
                    {
                        $moveNum = intval($imagesSetting['move_main_pic'])-1;
                        if(isset($carouselGallery[$moveNum]))
                        {
                            $first = $carouselGallery[0];
                            $replace = $carouselGallery[$moveNum];
                            unset($carouselGallery[0]);
                            $carouselGallery[0] = $replace;
                            $carouselGallery[$moveNum] = $first;
                            sort($carouselGallery);
                        }
                    }
                    break;
                case 2: //使用sku第一张图替换主图第一张
                    if(isset($sourceData->extend_data['sku_img']) && count($sourceData->extend_data['sku_img']))
                    {
                        $replaceImg = $sourceData->extend_data['sku_img'][0];
                        if(isset($replaceImg['skuImg']) && !empty($replaceImg['skuImg']))
                        {
                            $carouselGallery[0] = $replaceImg['skuImg'];
                        }
                    }
                    break;
                case 3: //随机打乱
                    //固定第一张图不打乱
                    if(isset($imagesSetting['random_fixed_first_main']) && $imagesSetting['random_fixed_first_main'] == 1)
                    {
                        $top = array_shift($carouselGallery);
                        shuffle($carouselGallery);
                        array_unshift($carouselGallery,$top);
                    }else{
                        shuffle($carouselGallery);
                    }
                    break;
            }
        }
        //图片是否压缩
        $compress = $filter->settings['compress']['pic_compress_percent'] ?? null;
        $imgSetting = [];
        $imgSetting['is_cut'] = true;
        $imgSetting['is_compress'] = true;
        $imgSetting['compress_percent'] = 80;
        if(isset($compress) && $compress < 100 && $compress >= 50)
        {

            $imgSetting['compress_percent'] = $compress;
        }
        if(isset($filter->settings['images']['main_avatar_setting']) && is_array($filter->settings['images']['main_avatar_setting']))
        {
            $mainSetting = $filter->settings['images']['main_avatar_setting'];
            $imgSetting = array_merge(CopyHelper::formatWaterSetting($mainSetting,$mainWater));
        }



        $mainWaterPic = [];
        if(isset($imagesSetting['main_pic_watermark_custom']) && !empty($imagesSetting['main_pic_watermark_custom']))
        {
            $mainWaterPic = explode(',',$imagesSetting['main_pic_watermark_custom']);
        }

        $this->_showLog('开始处理商品轮播图');
        $wg = new WaitGroup();
        $downloadImgArr = [];
        $carouselGallery = array_unique($carouselGallery);
        foreach ($carouselGallery as $k => $img)
        {
            $tmpImg = explode('.',$img);
            $ext = end($tmpImg);
            if(!in_array($ext,$this->allowImgExt)) continue;
            /**
             * 轮播图不需要太多，下载10张即可
             */
            if(($k+1) > $this->carouselImgMaxNum)
            {
                continue;
            }
            $imgSetting['is_water'] = true;
            if(!in_array($k+1,$mainWaterPic))
            {
                $imgSetting['is_water'] = false;
            }
            $wg->add();
            go(function () use ($wg,$img,$imgSetting, &$downloadImgArr) {

                ConsoleHelper::runInfo('正在下载图片:'.$img);
                if(substr($img,0,2) == '//'){
                    $img = 'https:'.$img;
                }

                $imgInfo = PddSpec::processImage($img,$imgSetting);
                if($imgInfo)
                {
                    //轮播图要求 等宽高且大于480px,大小1M内
                    list($processImg,$width,$height,$size) = $imgInfo;
//                    if($width != $height )
//                    {
//                        PddSpec::delLocalImg($processImg);
//                    }
                    array_push($downloadImgArr,[
                        'path' => $processImg,
                        'width' => $width,
                        'height' => $height,
                        'size' => $size,
                    ]);
                }
            });
            $wg->done();
        }
        $wg->wait();
        if(count($downloadImgArr))
        {
            foreach ($downloadImgArr as $k =>  $img)
            {
                if(file_exists($img['path']))
                {
                    $this->_showLog('正在上传第'.($k+1).'张');
                    $gallery = $copyServer->uploadImageToPdd($img['path'],$mall_id);
                    array_push($copyData['carousel_gallery'],$gallery);
                }

            }
        }
//        foreach($carouselGallery as $k => $gallery)
//        {
//            /**
//             * 轮播图超过10张的自动跳过
//             */
//            if(count($copyData['carousel_gallery']) > $this->carouselImgMaxNum)
//            {
//                continue;
//            }
//            $this->_showLog('正在上传第'.($k+1).'张');
//            $imgSetting['is_water'] = true;
//            if(!in_array($k+1,$mainWaterPic))
//            {
//                $imgSetting['is_water'] = false;
//            }
//            $imgInfo = PddSpec::processImage($gallery,$imgSetting);
//            if(!$imgInfo) {
//                $this->_showLog('图片超过1M过大，直接跳过');
//                continue;
//            }
//            list($processImg,$width,$height,$size) = $imgInfo;
//            if($width != $height )
//            {
//                PddSpec::delLocalImg($processImg);
//                continue;
//            }
//
//            $gallery = $copyServer->uploadImageToPdd($processImg,$mall_id);
//            PddSpec::delLocalImg($processImg);
//            array_push($copyData['carousel_gallery'],$gallery);
//        }
        if(count($copyData['carousel_gallery']) == 0)
        {
            throw new CopyException('商品轮播图均不合规');
        }
        $this->_showLog('商品轮播图上传结束');
//        $copyData['carousel_gallery'] = StringHelper::jsonEncode($copyData['carousel_gallery']);
        if(isset($this->sourceData->extend_data['video']['video_url']) && !empty($sourceData->extend_data['video']['video_url'])
        )
        {
            $copyData['carousel_video'] = [];
            $copyData['carousel_video']['file_id'] = $sourceData->extend_data['video']['file_id'] ?? '';
            $copyData['carousel_video']['video_url'] = $sourceData->extend_data['video']['video_url'] ?? '';

            $copyData['carousel_video'] = StringHelper::jsonEncode($copyData['carousel_video']);
            $copyData['carousel_video_url'] = $this->sourceData->extend_data['video']['video_url'] ?? '';
        }

        return $copyData;
    }

    /**
     * 商品详情
     * @param ComSpider $sourceData
     * @param CopyService $copyServer
     * @param PddFilterTpl $filter
     * @param int $mall_id
     * @param string $water
     * @return array|bool
     * @since 下载改成协程处理。
     * @throws \yii\base\Exception
     */
    public function detail(ComSpider $sourceData,CopyService $copyServer,PddFilterTpl $filter,int $mall_id,string $water=null)
    {

        $filterSetting = $filter->settings['desc'];
        $copyData = [];
        $detailImages = $sourceData->extend_data['detail_gallery'];
        //商品详情图
        $copyData['detail_gallery'] = [];

        $detailNum = count($detailImages);
        //头部删除
        if(isset($filterSetting['desc_del_pre_imgs_num']) && $filterSetting['desc_del_pre_imgs_num'] > 0)
        {
            $delPicPreNum = intval($filterSetting['desc_del_pre_imgs_num']);
            if($detailNum > $delPicPreNum)
            {
                array_splice($detailImages,0,$delPicPreNum);
            }
        }
        //尾部删除
        if(isset($filterSetting['desc_del_after_imgs_num']) && $filterSetting['desc_del_after_imgs_num'] > 0)
        {
            $delPicAfterNum = intval($filterSetting['desc_del_after_imgs_num']);

            if($detailNum > $delPicAfterNum && $delPicAfterNum > 0)
            {
                array_splice($detailImages,-$delPicAfterNum);
            }
        }
        //图片是否压缩
        $compress = $filter->settings['compress']['pic_compress_percent'] ?? null;
        $imgSetting = [];
        $imgSetting['is_water'] = false;
        $imgSetting['is_compress'] = true;
        $imgSetting['compress_width'] = 600; //按600宽度缩放
        if(isset($compress) && $compress < 100 && $compress >= 50)
        {

            $imgSetting['compress_percent'] = $compress;
        }


        /**
         * 详情图水印设置
         * @since 修复详情图没有打水印问题
         */
        if($filter->settings['images']['detail_watermark_setting'] == 2 && isset($filter->settings['images']['detail_avatar_setting'])
        && is_array($filter->settings['images']['detail_avatar_setting'])
        )
        {
            $imgSetting = array_merge(CopyHelper::formatWaterSetting($filter->settings['images']['detail_avatar_setting'],$water));
            $imgSetting['is_water'] = true;
        }

        $this->_showLog('开始处理商品详情图');


        $detailImages = array_unique($detailImages);

        $wg = new WaitGroup();
        $downloadImgArr = [];
        foreach ($detailImages as $k => $img)
        {
            if($tmpImgRet = substr($img,0,2) == '//'){
                $img = 'https:'.$img;
            }
            $tmpImg = explode('.',$img);
            $ext = end($tmpImg);
            if(!in_array($ext,$this->allowImgExt)) continue;
            $wg->add();
            go(function () use ($wg,$img,$imgSetting, &$downloadImgArr) {
                ConsoleHelper::runInfo('正在下载详情图片:'.$img);
                $imgInfo = PddSpec::processImage($img,$imgSetting);
                if($imgInfo)
                {
                    list($processImg,$width,$height,$size) = $imgInfo;
                    //宽度480以上并且小于1200，大小1M以内,测试1:3 是个误会，改成1：2
                    if($width < 480 || $width > 1200 ||  ImagesHelper::sizeToM($size) > 1)
                    {
                        PddSpec::delLocalImg($processImg);
                    }else{
                        array_push($downloadImgArr,[
                            'path' => $processImg,
                            'width' => $width,
                            'height' => $height,
                            'size' => $size,
                        ]);
                    }
                }
            });
            $wg->done();
        }
        $wg->wait();

        foreach($downloadImgArr as $k =>$img)
        {
            if(count($copyData['detail_gallery']) >= $this->detailImgMaxNum)
            {
                continue;
            }
            if($img['width']*2.5 < $img['height']) {
                $cutList = ImagesHelper::cutImagesByHeight($img['path'],$img['width']*2);
                if(count($cutList))
                {
                    foreach($cutList as $i => $cutImg)
                    {
                        $this->_showLog('详情图过长，裁剪后正在上传'.($i+1).'张详情图');
                        $uploadCutImg = $copyServer->uploadImageToPdd($cutImg,$mall_id);
                        array_push($copyData['detail_gallery'],$uploadCutImg);
                    }
                    continue;
                }
            }
            $this->_showLog('正在上传第'.($k+1).'张详情图');
            try {
                $uploadImg = $copyServer->uploadImageToPdd($img['path'],$mall_id);
//            PddSpec::delLocalImg($img['path']);
                array_push($copyData['detail_gallery'],$uploadImg);
            }catch (\yii\base\Exception $e) {
                continue;
            }

        }

//        foreach($detailImages as $k =>$img)
//        {
//            $tmpImg = explode('.',$img);
//            $ext = end($tmpImg);
//            if(!in_array($ext,$this->allowImgExt)) continue;
//            if(count($copyData['detail_gallery']) >= $this->detailImgMaxNum)
//            {
//                continue;
//            }
//            $imgInfo = PddSpec::processImage($img,$imgSetting);
//            if(!$imgInfo) {
//                $this->_showLog('图片超过1M过大，直接跳过');
//                continue;
//            }
//            list($processImg,$width,$height,$size) = $imgInfo;
//            //宽度480px以上，大小1M以内,测试1:3 是个误会，改成1：2
//            if($width < 480 || ImagesHelper::sizeToM($size) > 1)
//            {
//                PddSpec::delLocalImg($processImg);
//                continue;
//            }
//            //将长图裁剪为多张图再次上传
//            if($width*2.5 < $height) {
//                $cutList = ImagesHelper::cutImagesByHeight($processImg,$width*2);
//                if(count($cutList))
//                {
//                    foreach($cutList as $i => $cutImg)
//                    {
//                        $this->_showLog('详情图过长，裁剪后正在上传'.($i+1).'张详情图');
//                        $img = $copyServer->uploadImageToPdd($cutImg,$mall_id);
//                        array_push($copyData['detail_gallery'],$img);
//                    }
//                    continue;
//                }
//            }
//            $this->_showLog('正在上传第'.($k+1).'张详情图');
//            $img = $copyServer->uploadImageToPdd($processImg,$mall_id);
//            PddSpec::delLocalImg($processImg);
//            array_push($copyData['detail_gallery'],$img);
//        }

        if(count($copyData['detail_gallery']) == 0)
        {
            return false;
        }
        $copyData['detail_gallery'] = StringHelper::jsonEncode($copyData['detail_gallery']);
        $this->_showLog('商品详情图上传结束');



        return $copyData;
    }


    /**
     * 商品文字详情
     * @param ComSpider $sourceData
     * @return bool|false|string|string[]|null
     */
    public function goodsDesc(ComSpider $sourceData)
    {
        //剔除描叙中的特殊符号、空格、换行等
        $desc = str_replace(["\\",'"',"\r\n","\n"," ","&nbsp;"],'', strip_tags($sourceData->extend_data['pc_desc']));

        //商品描叙超过500个做尾部截取操作
        $contents = trim($desc);

        //前缀
        if(isset($filterSetting['desc_header_html']) && !empty($filterSetting['desc_header_html']))
        {
            $contents = trim($filterSetting['desc_header_html']).$contents;
        }
        //后缀
        if(isset($filterSetting['desc_button_html']) && !empty($filterSetting['desc_button_html']))
        {
            $contents = $contents.trim($filterSetting['desc_button_html']);
        }

        //描叙为空使用标题作为描叙内容
        if(empty($contents))
        {
            $contents = trim($sourceData->extend_data['title']);
        }

        if(StringHelper::calLenByGBK($contents) > 500)
        {
            $contents = StringHelper::strCutByGBK($contents,60);
        }
        return $contents;
    }




    /**
     * 输出错误信息
     * @param string $msg
     */
    public function _showLog(string $msg)
    {
        ConsoleHelper::runInfo($this->spiderId.':copy:'.$msg);
        $this->logger->add($this->spiderId.':copy:'.$msg);
    }

}